package com.study.custom.mybatis;

import java.beans.PropertyDescriptor;
import java.lang.reflect.Method;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import java.util.ArrayList;
import java.util.List;

/**
 * @desc:
 * @author: panxiyi
 * @date: 2023/12/23 23:00
 */

public class Converter {
    /**
     * 这个方法，是将结果集中的每一条数据封装到一个JavaBean中，多条数据就对应多个JavaBean，再将多个       JavaBean放到一个List集合中
     * @param set
     * @param clazz
     * @param <E>
     * @return
     */
    public static <E> List<E> converList(ResultSet set, Class clazz){
        List<E> beans = new ArrayList<E>();
        //1.遍历结果集
        try {
            //根据结果集元数据，获取结果集中的每一列的列名
            ResultSetMetaData metaData = set.getMetaData();
            int columnCount = metaData.getColumnCount();//获取总列数
            while (set.next()){
                //每次遍历，遍历出一条数据，每条数据就对应一个JavaBean对象
                E o = (E) clazz.newInstance();
                //获取每一列数据，根据列名获取
                //for循环遍历出每一列
                for(int i=1; i<=columnCount; i++){
                    String columnName = metaData.getColumnName(i);
                    Object value = set.getObject(columnName);//获取该列的值
                    //将该列的值存放到JavaBean中
                    //也就是调用JavaBean的set方法,使用内省机制
                    PropertyDescriptor descriptor = new PropertyDescriptor(columnName,clazz);
                    Method writeMethod = descriptor.getWriteMethod();//获取该属性的set方法

                    //获取set方法的参数类型
                    Class<?> type = writeMethod.getParameterTypes()[0];

                    //调用set方法
                    writeMethod.invoke(o, getCastValueType(type, value));
                }
                //经过这个for循环，我的JavaBean就设置好了
                //把JavaBean添加进list集合
                beans.add(o);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return beans;
    }

    public static <E> E conver(ResultSet set, Class clazz){
        try {
            ResultSetMetaData metaData = set.getMetaData();
            int columnCount = metaData.getColumnCount();//获取总列数
            while (set.next()){
                E o = (E) clazz.newInstance();
                for(int i=1; i<=columnCount; i++){
                    String columnName = metaData.getColumnName(i);
                    Object value = set.getObject(columnName);
                    PropertyDescriptor descriptor = new PropertyDescriptor(columnName,clazz);
                    Method writeMethod = descriptor.getWriteMethod();
                    Class<?> type = writeMethod.getParameterTypes()[0];
                    Object castValue = getCastValueType(type, value);
                    //调用set方法
                    writeMethod.invoke(o, castValue);
                }
                return o;
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }


    static Object getCastValueType(Class<?> type, Object value) {
        Object castValue;
        if (type.isAssignableFrom(value.getClass())) {
            castValue = value;
        } else {
            //如果value类型与set方法参数类型不同，尝试做类型转换
            if (type == Integer.TYPE || type == Integer.class) {
                castValue = Integer.parseInt(String.valueOf(value));
            } else if (type == Boolean.TYPE || type == Boolean.class) {
                castValue = Boolean.parseBoolean(String.valueOf(value));
            } else if (type == Long.TYPE || type == Long.class) {
                castValue = Long.parseLong(String.valueOf(value));
            } else if (type == Float.TYPE || type == Float.class) {
                castValue = Float.parseFloat(String.valueOf(value));
            } else if (type == Double.TYPE || type == Double.class) {
                castValue = Double.parseDouble(String.valueOf(value));
            } else if (type == Short.TYPE || type == Short.class) {
                castValue = Short.parseShort(String.valueOf(value));
            } else if (type == Byte.TYPE || type == Byte.class) {
                castValue = Byte.parseByte(String.valueOf(value));
            } else if (type == Character.TYPE || type == Character.class) {
                castValue = value.toString().charAt(0);
            } else {
                //默认为String类型
                castValue = String.valueOf(value);
            }
        }
        return castValue;
    }
}
